package it.polimi.traveldream.ejb.eaos;

import java.util.List;

import it.polimi.traveldream.ejb.dtocreator.UserDTOCreator;
import it.polimi.traveldream.ejb.entities.User;
import it.polimi.traveldream.ejbclient.dtos.UserDTO;
import it.polimi.traveldream.ejbclient.eaos.AccountServiceEAO;
import it.polimi.traveldream.utils.enums.UserRole;
import it.polimi.traveldream.utils.exceptions.NotSuchUserException;
import it.polimi.traveldream.utils.exceptions.NotUniqueUserException;

import javax.annotation.Resource;
import javax.annotation.security.RolesAllowed;
import javax.ejb.EJBContext;
import javax.ejb.Stateless;
import javax.persistence.EntityManager;
import javax.persistence.NoResultException;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;

/**
 * Session Bean implementation class AccountService
 */
@Stateless
public class AccountService implements AccountServiceEAO {
	@PersistenceContext
	private EntityManager entityManager;
	@Resource
	private EJBContext ejbContext;

	@Override
	public void registerUser(UserDTO user) throws NotUniqueUserException {
		try {
			getUser(user.getEmail());
			throw new NotUniqueUserException();
		} catch (NotSuchUserException e) {
			User newUser = new User(user);
			entityManager.persist(newUser);
		}
	}

	@RolesAllowed({UserRole._ADMINISTRATOR})
	@Override
	public void unregisterUser(int userId) throws NotSuchUserException {
		User removeUser = entityManager.find(User.class, userId);
		if(removeUser != null) {
			entityManager.remove(removeUser);
		} else {
			throw new NotSuchUserException();
		}
	}

	@SuppressWarnings("unchecked")
	@RolesAllowed({UserRole._ADMINISTRATOR})
	@Override
	public List<UserDTO> getUsers(UserRole role) {
		Query q = entityManager.createNamedQuery(User.FIND_USERS_BY_ROLE);
		q.setParameter("role", role);
		return UserDTOCreator.createUserList((List<User>) q.getResultList());
	}

	@RolesAllowed({UserRole._CUSTOMER,UserRole._EMPLOYEE, UserRole._ADMINISTRATOR})
	@Override
	public UserDTO getUser(String email) throws NotSuchUserException{
		Query q = entityManager.createNamedQuery(User.FIND_USER_BY_EMAIL);
		q.setParameter("email", email);
		try {
			User user = (User) q.getSingleResult();
			return UserDTOCreator.createUser(user);
		}
		catch (NoResultException e) {
			throw new NotSuchUserException();
		}
	}
	
	@RolesAllowed({UserRole._CUSTOMER,UserRole._EMPLOYEE, UserRole._ADMINISTRATOR})
	@Override
	public UserDTO getCurrentUser() {
		String userEmail = ejbContext.getCallerPrincipal().getName();
		try {
			return getUser(userEmail);
		} catch (NotSuchUserException e) {
			e.printStackTrace();
			return null;
		}
	}
	
}
